package relop;

import global.RID;
import global.SearchKey;
import heap.HeapFile;
import index.HashIndex;
import index.HashScan;

/**
 * Wrapper for hash scan, an index access method.
 */
public class KeyScan extends Iterator {
	HashScan h_scan;
	HashIndex h_index;
	HeapFile hf;
	SearchKey skey;

	/**
	 * Constructs an index scan, given the hash index and schema.
	 */
	public KeyScan(Schema schema, HashIndex index, SearchKey key, HeapFile file) {
		//throw new UnsupportedOperationException("Not implemented");
		this.schema = schema;
		h_index = index;
		skey = key;
		hf = file;
		h_scan = h_index.openScan(skey);
	}

	/**
	 * Gives a one-line explaination of the iterator, repeats the call on any
	 * child iterators, and increases the indent depth along the way.
	 */
	/**
	 * Print out the features that the iterator is working on. 
	 * For example, if you are explaining a scan, print out the index and file. 
	 * If you are explaining a projection, print out the details of the fields.
	 * Just remember, if other iterators are part of your class, you have to call 
	 * the explain function of them at the end too (with the parameter "depth+1")*/

	public void explain(int depth) {
		//throw new UnsupportedOperationException("Not implemented");
		System.out.printf("For the keyScan, the hashIndex now is %s", h_index.toString());
		System.out.printf("                 the heapFile now is %s", hf.toString());

	}

	/**
	 * Restarts the iterator, i.e. as if it were just constructed.
	 */
	public void restart() {
		//throw new UnsupportedOperationException("Not implemented");
		if(h_scan!=null) h_scan.close(); 
		h_scan = h_index.openScan(skey);
	}

	/**
	 * Returns true if the iterator is open; false otherwise.
	 */
	public boolean isOpen() {
		//throw new UnsupportedOperationException("Not implemented");
		if(h_scan!=null) return true;
		else return false;
	}

	/**
	 * Closes the iterator, releasing any resources (i.e. pinned pages).
	 */
	public void close() {
		//throw new UnsupportedOperationException("Not implemented");
		if(h_scan!=null) h_scan.close();
	}

	/**
	 * Returns true if there are more tuples, false otherwise.
	 */
	public boolean hasNext() {
		//throw new UnsupportedOperationException("Not implemented");
		if(h_scan!=null) {
			if(h_scan.hasNext()==true)
				return true;
			else 
				return false;
		}
		else 
			return false;
	}

	/**
	 * Gets the next tuple in the iteration.
	 * 
	 * @throws IllegalStateException if no more tuples
	 */
	public Tuple getNext() {
		//throw new UnsupportedOperationException("Not implemented");

		if(h_scan!=null){
			RID rid = h_scan.getNext();
			Tuple wanted = new Tuple(this.schema, hf.selectRecord(rid));
			return wanted;
		}
		else 
			return null;

	}

} // public class KeyScan extends Iterator
